﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Net;
using System.Net.Sockets;
using System.Threading;
using System.Runtime.InteropServices;
//using System.Net.NetworkInformation;
//using System.Timers;


namespace ProtocolConversion_WINCE
{
    public partial class Form1 : Form
    {
        //注意事项
        /// <summary>
        /// 数据出现错误程序不能停止，程序有自启动
        /// </summary>
        #region 字段
        //委托
        private delegate void TextChangeEvent();//代理控件线程调度
        //处理文本委托调用
        private delegate void OnMessageChangeEvent();
        private event OnMessageChangeEvent OnMessageChange;
        
        public delegate void AppendStringDelegate(string str);
        public AppendStringDelegate appendstringdelegate;
        //线程
        private Socket clientSocket1;//login socket;
        private Socket clientSocket2;//date socket
        //字典存储数据
        private Dictionary<byte[], byte[]> dateByteDic = new Dictionary<byte[], byte[]>();//存储收到的数据信息，根据CMD取出相应的数据
        private Dictionary<string, byte[]> cmdByteDic = new Dictionary<string, byte[]>();//存储需要发送的指令
        public static Dictionary<string, byte[]> ReturnFrameCMDByteDic = new Dictionary<string, byte[]>();//存储接收数据帧类类型
        public static Dictionary<string, byte[]> checkoutByteDic = new Dictionary<string, byte[]>();
        //登陆线程
        private Thread t;
        //数据线程
        private Thread t2;
        //form2对话框对象
        BDForm bdForm;
        //ping对象
        private Ping ping;
        //socket1是否链接标志位
        private bool isConnected = false;
        //socket2是否链接标志位
        private bool clientSocket2IsConnected = false;
        //ping标志
        private bool isOnline = false;
        //重新链接标志
        private bool isReconnected = false;
        //重新链接成功标志位
        private static bool isLine = false;            
        private bool isUseBD = false;//是否使用北斗传输数据
        private bool isEnableWDT = false;
        //存储socket2端口信息
        private static int port = 8000;
        //命令字节数组
        private byte[] date = new byte[2048];//clientSocket1
        private byte[] date2 = new byte[2048];//clieintSocket2
        //同步字
        private byte[] SYNC = new byte[4] { 0xbf, 0x13, 0x97, 0x74 };
        //待发送的28字节
        public static byte[] dateSend = new byte[28];
        //北斗反馈帧字节数组
        private byte[] returnDateByte_BD = new byte[14];
        //获取台站信息
        private byte[] stationDate = new byte[] { 0xbf, 0x13, 0x97, 0x74, 0x00, 0x00, 0x00, 0x80, 0x04, 0x00, 0x00, 0x00, 0xfc, 0x7f };
        
        private byte[] rtson = new byte[] { 0x52, 0x54, 0x53, 0x20, 0x4f, 0x4e, 0x0d, 0x0a };
        //登陆使能        
        private byte[] rstaton = new byte[] { 0x52, 0x53, 0x54, 0x41, 0x54, 0x20, 0x4f, 0x4e, 0x0d, 0x0a };
        //用户名
        private byte[] rootDate = new byte[] { 0x72, 0x6f, 0x6f, 0x74, 0x0d, 0x0a };
        //密码
        private byte[] secretDate = new byte[] { 0x61, 0x72, 0x63, 0x61, 0x31, 0x30, 0x30, 0x0d, 0x0a };
        //存储空间
        private byte[] memorySizeDate = new byte[] { 0xbf, 0x13, 0x97, 0x74, 0x00, 0x00, 0x67, 0x80, 0x04, 0x00, 0x00, 0x00, 0x95, 0x7f };
        //电压
        private byte[] powerPressureDate = new byte[] { 0xbf, 0x13, 0x97, 0x74, 0x00, 0x00, 0x66, 0x80, 0x04, 0x00, 0x00, 0x00, 0x96, 0x7f };
        //GPS
        private byte[] gpsDate = new byte[] { 0xbf, 0x13, 0x97, 0x74, 0x00, 0x00, 0x65, 0x80, 0x04, 0x00, 0x00, 0x00, 0x97, 0x7f };
        //温度
        private byte[] tempertureDate = new byte[] { 0xbf, 0x13, 0x97, 0x74, 0x00, 0x00, 0x62, 0x80, 0x04, 0x00, 0x00, 0x00, 0x9a, 0x7f };
        //总信息
        private byte[] totalDate = new byte[] { 0xbf, 0x13, 0x97, 0x74, 0x00, 0x00, 0x00, 0x80, 0x04, 0x00, 0x00, 0x00, 0xfc, 0x7f, //station
                                               
                                                0xbf, 0x13, 0x97, 0x74, 0x00, 0x00, 0x62, 0x80, 0x04, 0x00, 0x00, 0x00, 0x9a, 0x7f ,//temperature
                                                
                                                0xbf, 0x13, 0x97, 0x74, 0x00, 0x00, 0x67, 0x80, 0x04, 0x00, 0x00, 0x00, 0x95, 0x7f, //memorysize

                                                0xbf, 0x13, 0x97, 0x74, 0x00, 0x00, 0x65, 0x80, 0x04, 0x00, 0x00, 0x00, 0x97, 0x7f };//gps
        
        //接收message信息
        private string message;
        //委托调用
        private string textMessage;
        public string TextMessage
        {
            set
            {
                if (value == null || OnMessageChange == null)
                    return;
                textMessage = value;
                OnMessageChange();
               
            }
        }

        private long time = 0;
        private long time2 = 0;//用于给服务器重新链接计时
        private long time3 = 0;//超时重启系统计时器
        private int wdtTime = 0;//看门狗计时器
        private static long disconnectedIndex = 0;//容错变量 
        //北斗通信终端ID（北斗卡号）
        private string ID = "123456";
        public BDCommunication bdCommunication;
        
        #endregion

        public Form1()
        {
            InitializeComponent();
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            Init();
            Login();
            //Control.CheckForIllegalCrossThreadCalls = false;
            WDT.StartWDT();//启动看门狗
            isEnableWDT = true;
        }
        //登陆到服务器
        private void Login()
        {
            while (!ping.GetPingResult()) ;//wati until connected to server

            try
            {
                if (clientSocket1 == null)
                    clientSocket1 = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
                if (clientSocket1.Poll(10, SelectMode.SelectRead))
                {
                    clientSocket1.Shutdown(SocketShutdown.Both);
                }
                clientSocket1.Connect(new IPEndPoint(IPAddress.Parse(textBox1.Text), int.Parse(textBox2.Text)));
                textBox4.Text += "server is connected\r\n";
                isConnected = true;
            }
            catch
            {
                MessageBox.Show("Connect server failed!\r\n");
                isConnected = false;
            }
            if (isConnected)
            {
                t = new Thread(GetServerthreadInfo);
                t.IsBackground = true;
                t.Start();
                t2 = new Thread(GetDateThreadInfo);
                t2.IsBackground = true;
                t2.Start();
            }
        }
        //初始化信息
        private void Init()
        {
            InitCMDAndReturnFrameCMDByteDic();
            PackageHead();
            PackageBDHead();
            Communication.InitPort();//初始化端口：
            textBox4.Text += "端口已经打开"+Environment .NewLine ;
            TimeInit();//初始化定时器
            ping = new Ping();//实例化ping对象
            bdCommunication = new BDCommunication(this);//实例化北斗对象
            OnMessageChange += this.Form1_OnMessageChange;//注册textbox委托
            appendstringdelegate = new AppendStringDelegate(AppendString);
            bdForm = new BDForm(this);//实例化北斗对象
            btnDisUseBD.Enabled = false;//禁用北斗按钮失能
            //初始化窗体的位置
            Rectangle rect = Screen.PrimaryScreen.WorkingArea;
            int width, height;
            width = (rect.Width - this.Size.Width) / 2;
            height = (rect.Height - this.Size.Height) / 2;
            this.Location = new Point(width, height);

        }
        //初始化定时器
        private void TimeInit()
        {
            timer1.Interval = 2000;
            timer1.Enabled = true;
            timer2.Interval = 1000;
            timer2.Enabled = true;
        }
        //跨线程调用UI控件
        public void AppendString(string value)
        {
            if (textBox4.InvokeRequired)
            {
                AppendStringDelegate d = new AppendStringDelegate(AppendString);
                textBox4.Invoke(d, value);
            }
            else
            {
                textBox4.Select(textBox4.TextLength, 0);
                textBox4.ScrollToCaret();
                textBox4.Text += value + Environment.NewLine;
            }
        }
        //接收socket1的登陆信息
        private void GetServerthreadInfo()
        {

            while (isConnected)
            {
                try
                {
                    int length;
                    Array.Clear(date, 0, date.Length);
             
                        length = clientSocket1.Receive(date);
                        message = Encoding.ASCII.GetString(date, 0, length);
                        //AppendString(message);
                }
                catch
                {
                    AppendString("clientSocket1 为空！");
                }
                if (message == "100 connection accepted, login:\r\n")
                {
                    clientSocket1.Send(rootDate);
                    //AppendString(message);
                }
                if (message == "102 password for root:\r\n")
                {
                    clientSocket1.Send(secretDate);
                    //AppendString(message);
                    for (int i = 0; i < 8000000; i++) ;
                    //链接必须发送的使能字节，不发送则无法接收数据
                    clientSocket1.Send(rstaton);
                }
                if (message == "107 check passed, to create data link.\r\n108 8000 is data port.\r\n" || message == "108 8000 is data port.\r\n")
                {
                    port = 8000;
                    
                    if (clientSocket2 == null)
                    {
                        clientSocket2 = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);                       
                    }
                    try
                    {
                        clientSocket2.Connect(new IPEndPoint(IPAddress.Parse("10.34.161.99"), port));
                        
                        AppendString("lientSocket2 is connected!\t端口号：" + port );
                        clientSocket2IsConnected = true;           
                        if (isReconnected)
                        {
                            isReconnectedSucess = true;
                        }

                    }
                    catch
                    {
                        
                        AppendString("clientSocket2 is DisConnected!");
                        clientSocket2IsConnected = false;
                        isReconnectedSucess = false;
                        //isReconnectedSucess = false;
                    }
                }
                if (message == "107 check passed, to create data link.\r\n108 8001 is data port.\r\n" || message == "108 8001 is data port.\r\n")
                {
                    port = 8001;
                    if (clientSocket2 == null)
                    {
                        clientSocket2 = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
                    }
                    try
                    {
                        clientSocket2.Connect(new IPEndPoint(IPAddress.Parse("10.34.161.99"), port));

                        AppendString("lientSocket2 is connected!\t端口号：" + port);
                        clientSocket2IsConnected = true;
                        timer1.Enabled = true;

                        if (isReconnected)
                        {
                            isReconnectedSucess = true;
                        }
                    }
                    catch
                    {
                        
                        AppendString("clientSocket2 is DisConnected!");
                        clientSocket2IsConnected = false;
                        isReconnectedSucess = false;
                        //isReconnectedSucess = false;
                    }
                }
                if (message == "107 check passed, to create data link.\r\n108 8002 is data port.\r\n" || message == "108 8002 is data port.\r\n")
                {
                    port = 8002;
                    if (clientSocket2 == null)
                    {
                        clientSocket2 = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
                    }
                    try
                    {
                        clientSocket2.Connect(new IPEndPoint(IPAddress.Parse("10.34.161.99"), port));

                        AppendString("lientSocket2 is connected!\t端口号：" + port);
                        clientSocket2IsConnected = true;
                        timer1.Enabled = true;

                        if (isReconnected)
                        {
                            isReconnectedSucess = true;
                        }
                    }
                    catch
                    { 
                        AppendString("clientSocket2 is DisConnected!");
                        clientSocket2IsConnected = false;
                        isReconnectedSucess = false;
                        //isReconnectedSucess = false;
                    }
                }
                if (message == "107 check passed, to create data link.\r\n108 8003 is data port.\r\n" || message == "108 8003 is data port.\r\n")
                {
                    port = 8003;
                    if (clientSocket2 == null)
                    {
                        clientSocket2 = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
                    }
                    try
                    {
                        clientSocket2.Connect(new IPEndPoint(IPAddress.Parse("10.34.161.99"), port));

                        AppendString("lientSocket2 is connected!\t端口号：" + port);
                        clientSocket2IsConnected = true;
                        timer1.Enabled = true;

                        if (isReconnected)
                        {
                            isReconnectedSucess = true;
                        }
                    }
                    catch
                    {
                        
                        AppendString("clientSocket2 is DisConnected!");
                        clientSocket2IsConnected = false;
                        isReconnectedSucess = false;
                        //isReconnectedSucess = false;
                    }
                }
            }
        }
        //接收socket2 的数据信息
        private void GetDateThreadInfo()
        {
            while (true)
            {
                if (clientSocket2IsConnected)
                {
                    int length;
                    Array.Clear(date2, 0, date2.Length);
                    try
                    {
                        length = clientSocket2.Receive(date2);
                    }
                    catch 
                    {
                        continue;
                    }
                    //message = Encoding.ASCII.GetString(date2, 0, length);
                    if (!(CompareDate(Converter.TakeOutByteNoOrder(date2, 6, 2), new byte[2] { 0xdd, 0x55 })))
                    {
                        //SegmentMessage(date2, length);
                        SelectFragment(date2, length);
                    }
                }               
            }
        }        
        //定位不同的数据，将数据传到指定的类(数采）
        public void SegmentMessage(byte[] date, int length)
        {
            if (!CompareDate(Converter.TakeOutByteNoOrder(date, 0, 4), new byte[] { 0xbf, 0x13, 0x97, 0x74 })) return;//不排序
            byte[] cmd = Converter.TakeOutByteNoOrder(date, 6, 2);
            switch (BitConverter.ToInt16(cmd, 0))
            {
                //电压
                case 0x7066:
                    //case 0x7000:
                    PowerPressure.SegmentMessage(date, length, "电压");//length zhi dai que ding
                    break;
                //温度
                case 0x7062:
                    Temperture.SegmentMessage(date, length, "温度");//length zhi dai que ding
                    break;
                //存储空间
                case 0x7067:
                    Memory.SegmentMessage(date, length, "存储空间");//length zhi dai que ding
                    break;
                //GPS
                case 0x7065:
                    GPS.SegmentMessage(date, length, "GPS");//length zhi dai que ding
                    break;
                default:
                    break;
            }

        }
        //提取北斗协议信息
        public void SegmentMessageForBD(byte[] date, int length)
        {
            if (!CRCCheckBD(date))
            {
                AppendString("校验字错误");
                CRCWrong_BD();//向北斗反馈crc校验错误信息
                return;
            }
            if (!CompareDate(Converter.TakeOutByteNoOrder(date, 0, 4), new byte[] { 0xbf, 0x13, 0x97, 0x74 })) return;//不排序
            byte[] cmd = Converter.TakeOutByteNoOrder(date, 8, 2);
            switch (BitConverter.ToInt16(cmd, 0))
            {
                //（收到了数据帧）发送状态信息到监控中心
                case 0x1001:
                    AppendString("收到数据:0x1001\t正在通过北斗发送数据");
                    RegularlySending();//先获取数据
                    bdCommunication.SingleCommunication_byte(ID, dateSend);
                    AppendString("数据发送成功");
                    //已经向中心台站发送数据就不需要再发送反馈帧了
                    break;
                //重启地震数据采集器
                case 0x2001:
                    AppendString("收到数据:0x2001\t正在正在执行重启指令");
                    GPIO.RestartDevice(0x2001, 1);//高电平重启
                    sendReturnDateToBD();
                    break;
                //重启前兆数据采集器
                case 0x2002:                  
                    AppendString("收到数据:0x2002\t正在正在执行重启指令");
                    GPIO.RestartDevice(0x2002, 1);
                    sendReturnDateToBD();
                    break;
                //重启电科控制主机
                case 0x2003:
                    AppendString("收到数据:0x2003\t正在正在执行重启指令");
                    GPIO.RestartDevice(0x2003, 1);
                    sendReturnDateToBD();
                    break;
                //重启终端设备
                case 0x2004:
                    AppendString("收到数据:0x2004\t正在正在执行重启指令");
                    GPIO.RestartDevice(0x2004, 1);
                    sendReturnDateToBD();
                    break;
                //重启总控
                case 0x2005:
                    break;
                case 0x3001:
                    //确认收到了反馈，则不需要重新发送
                    break;
                //设置帧反馈
                case 0x3002:
                    break;
                //crc校验出错反馈
                case 0x3003:
                    break;
                default:
                    break;
            }

        }
        //向北斗发送发聩信息
        private void sendReturnDateToBD()
        {
            FillDateToBD(new byte[] { 0x01, 0x30 }, 8, 2);
            CRCCalDateToBD(returnDateByte_BD, 1);
            bdCommunication.SingleCommunication_byte(ID, returnDateByte_BD);
            AppendString("数据发送成功");
        }
        //crc 校验出错时向中心发送反馈信息
        private void CRCWrong_BD()
        {
            //发送校验字错误反馈帧
            FillDateToBD(new byte[] { 0x02, 0x30 }, 8, 2);//3002
            CRCCalDateToBD(returnDateByte_BD, 1);
            bdCommunication.SingleCommunication_byte(ID, returnDateByte_BD);
        }
        //计算CRC,并将CRC结果添加到协议中
        /// <summary>
        /// 计算CRC,并将CRC结果添加到协议中
        /// </summary>
        /// <param name="source">被计算的数组</param>
        /// <param name="index">区分是哪个date</param>
        private void CRCCalDateToBD(byte[] source,int index)
        {
            unsafe
            {
                fixed (byte* p = &source[0])
                {
                     if(index == 0)//计算dateSend帧CRC
                    {
                        FillDate (CRC.CheckCRC (p,source .Length-2 ),source .Length -2,2);//向sendDate中添加数据
                    }
                    else if(index ==1 ) //计算反馈帧CRC
                    {
                        FillDateToBD (CRC .CheckCRC (p,source .Length -2),source .Length -2,2);//向反馈帧中添加CRC数据
                    }
                }
            }
        }
        //CRC校验BD协议
        /// <summary>
        /// CRC校验BD协议
        /// </summary>
        /// <param name="sourceDate">被校验的字节数组</param>
        /// <returns></returns>
        private bool CRCCheckBD(byte[] sourceDate)
        {
            unsafe
            {
                fixed (byte* p = &sourceDate[0])
                {
                    if (CompareDate(CRC.CheckCRC(p , sourceDate.Length - 2), new byte[] { sourceDate[12], sourceDate[13] }))
                        return true;
                }
            }
            return false;
        }
        //数据比较
        public static bool CompareDate(byte[] date1, byte[] date2)
        {
            if (date1.Length != date2.Length) return false;
            for (int i = 0; i < date1.Length; i++)
            {
                if (date1[i] != date2[i])
                {
                    return false;
                }
            }
            return true;
        }
        //初始化命令列表
        private void InitCMDAndReturnFrameCMDByteDic()
        {
            //CMD
            cmdByteDic.Add("电压", new byte[] { 0x61, 0x80 });
            cmdByteDic.Add("温度", new byte[] { 0x62, 0x80 });
            cmdByteDic.Add("存储空间", new byte[] { 0x67, 0x80 });
            cmdByteDic.Add("GPS", new byte[] { 0x65, 0x80 });

            //checkOut
            ReturnFrameCMDByteDic.Add("电压", new byte[] { 0x61, 0x70 });
            ReturnFrameCMDByteDic.Add("温度", new byte[] { 0x62, 0x70 });
            ReturnFrameCMDByteDic.Add("存储空间", new byte[] { 0x68, 0x70 });
            ReturnFrameCMDByteDic.Add("GPS", new byte[] { 0x65, 0x70 });
        }
        //封装数据采集协议头部
        private void PackageHead()
        {
            dateSend[0] = 0xbf;
            dateSend[1] = 0x13;
            dateSend[2] = 0x97;
            dateSend[3] = 0x74;
            dateSend[4] = 0x01;
            dateSend[5] = 0x00;
            dateSend[6] = 0x01;
            dateSend[7] = 0x00;
            dateSend[8] = 0x01;
            dateSend[9] = 0x10;
            dateSend[10] = 0x10;
            dateSend[11] = 0x00;
            dateSend[12] = 0xc0;
        }
        //封装北斗反馈帧协议头部
        private void PackageBDHead()
        {
             
            returnDateByte_BD[0] = 0xbf;
            returnDateByte_BD[1] = 0x13;
            returnDateByte_BD[2] = 0x97;
            returnDateByte_BD[3] = 0x74;
            returnDateByte_BD[4] = 0x01;
            returnDateByte_BD[5] = 0x00;
            returnDateByte_BD[6] = 0x01;
            returnDateByte_BD[7] = 0x00;
            returnDateByte_BD[8] = 0x00;//cmd
            returnDateByte_BD[9] = 0x00;
            returnDateByte_BD[10] = 0x02;//length
            returnDateByte_BD[11] = 0x00;
        }
        //向数采协议中添加数据（低位在前，高位在后）
        public static bool FillDate(byte[] date, int index, int length)
        {
            int j = 0;
            for (int i = index; i < index + length; i++)
            {
                if (i < dateSend.Length && i >= 0)
                {
                    dateSend[i] = date[j++];
                }
                else
                {
                    return false;
                }
            }
            return true;
        }
        //向北斗返回帧添加数据
        public bool FillDateToBD(byte[] date, int index, int length)
        {
            int j = 0;
            for (int i = index; i < index + length; i++)
            {
                if (i < returnDateByte_BD.Length && i >= 0)
                {
                    returnDateByte_BD[i] = date[j++];
                }
                else
                {
                    return false;
                }
            }
            return true;
        }
        //根据规格计算 DATE校验字
        public static byte[] CalculateCheckByte(byte[] date)
        {
            byte[] SENSOR_ID = new byte[2];
            byte[] CMD = new byte[2];
            byte[] LENGTH = new byte[2];
            byte[] UNUSED = new byte[2];

            return null;
        }
        //检查网络状态
        private void CheckNetSate()
        {

            if (clientSocket2 != null)
            {
                //if (clientSocket2.Poll(10, SelectMode.SelectRead ))
                //if(Ping1.ChectNet ())
                if(ping .GetPingResult())
                {
                    isOnline = true  ;
                }
                else
                {
                    isOnline = false ;
                }

                if (isOnline)
                {
                    FillDate(new byte[2] { 0xff, 0xff }, 16, 2);
                    isLine = true;
                    disconnectedIndex = 0;
                }
                else
                {
                    disconnectedIndex++;
                    if (disconnectedIndex > 2)
                    {
                        isLine = false;
                        FillDate(new byte[2] { 0x11, 0x11 }, 16, 2);
                    }
                    else
                    {
                        isLine = true;
                        FillDate(new byte[2] { 0xff, 0xff }, 16, 2);
                    }
                    
                }
            }
        }
        //按钮点击事件
        private void button2_Click(object sender, EventArgs e)
        {
            //clientSocket2IsConnected = false;
        }
        //填充协议
        private void CopyDate(byte[] date1, byte[] date2, int index, int length)
        {
            if (date2.Length < date1.Length)
            {
                int j = 0;
                for (int i = index; i < index + length && i < date1.Length; i++)
                {
                    date1[i] = date2[j++];
                }
            }
        }       
        //数据分片
        private void SelectFragment(byte[] date, int length)
        {
            int i = 0;
            for (int j = 0; j + 4 < length; j++)
            {
                if (CompareDate(Converter.TakeOutByteNoOrder(date, j, 4), SYNC))
                {
                    if (j != i && j > i)
                    {
                        byte[] dateTemp = Converter.TakeOutByteNoOrder(date, j, j - i);
                        SegmentMessage(dateTemp, j - i);
                        i = j;
                    }
                }
                else if ((i == 0) && (j + 4 == length - 1))
                {
                    SegmentMessage(date, length);
                    break;
                }
            }
        }
        //按钮点击事件
        private void button1_Click_1(object sender, EventArgs e)
        {

            //textBox4.Text += "开始查询\t\n";
            //if (clientSocket2IsConnected == false) return;
            clientSocket2IsConnected = false;//数据发送时锁定dateSend;
            //clientSocket2.Send(totalDate);
            clientSocket2.Send(memorySizeDate);

            clientSocket2.Send(memorySizeDate);
            Thread.Sleep(10);
            clientSocket2.Send(tempertureDate);
            Thread.Sleep(10);
            clientSocket2.Send(tempertureDate);
            Thread.Sleep(10);
            clientSocket2.Send(tempertureDate);
            Thread.Sleep(10);
            clientSocket2.Send(gpsDate);
            Thread.Sleep(10);
            clientSocket2.Send(gpsDate);
            Thread.Sleep(10);
            clientSocket2.Send(powerPressureDate);
            Thread.Sleep(10);
            clientSocket2.Send(powerPressureDate);
            CheckNetSate();
            CopyDate(dateSend, CRC.CRC16(dateSend), 26, 2);//计算校验字           
            Communication.SendMessage(dateSend, dateSend.Length);
            clientSocket2IsConnected = true;
        }
        //定时发送
        private void RegularlySending()
        {
            CheckNetSate();

            #region MyRegion

            if (isLine == false)
            {
                if (isConnected)
                    AppendString("网络链接断开，请确保网络通信正常!");//只显示一次
                isConnected = false;
                
                unsafe
                {
                    fixed (byte* p = &dateSend[0])
                    {
                        CopyDate(dateSend, CRC.CheckCRC(p, dateSend.Length - 2), 26, 2);
                    }
                }
                Communication.SendMessage(dateSend, dateSend.Length);//发送断开链接数据
                
            }
            else
            {
               // if (isConnected == false && isReconnected == false || isReconnectedSucess == false)
               if (isConnected == false && isReconnected == false )
                {
                    AppendString("网络恢复，正在重新链接...");
                    //重新链接服务器
                    //ReConnectedToServer();
                    WDT.ReBootSystem();//重启系统
                    
                }
                #region
              //clientSocket2IsConnected = false;//数据发送时锁定dateSend;
                try
                {
                    if (isConnected)
                    {
                        clientSocket2.Send(memorySizeDate);

                        clientSocket2.Send(memorySizeDate);
                        Thread.Sleep(10);
                        clientSocket2.Send(tempertureDate);
                        Thread.Sleep(10);
                        clientSocket2.Send(tempertureDate);
                        Thread.Sleep(10);
                        clientSocket2.Send(tempertureDate);
                        Thread.Sleep(10);
                        clientSocket2.Send(gpsDate);
                        Thread.Sleep(10);
                        clientSocket2.Send(gpsDate);
                        Thread.Sleep(10);
                        clientSocket2.Send(gpsDate);
                        Thread.Sleep(20);
                        clientSocket2.Send(gpsDate);
                        //clientSocket2.Send(powerPressureDate);
                        //Thread.Sleep(10);
                        //clientSocket2.Send(powerPressureDate);
                    }
                    
                }
                catch
                {
                    //return;
                }
                unsafe
                {
                    fixed (byte* p = &dateSend[0])
                    {
                        CopyDate(dateSend, CRC.CheckCRC(p, dateSend.Length - 2), 26, 2);
                    }

                }
                Communication.SendMessage(dateSend, dateSend.Length);

               // clientSocket2IsConnected = true;
                #endregion
            }
            #endregion

        }
        //服务器重新链接
        private void ReConnectedToServer()
        {
            //CloseSocket();
            //TimeInit();
            try
            {
                clientSocket2 = null;
                Socket clientSocket1Temp;
                Socket clientSocket2Temp;
                //Thread.Sleep(2000);
                //isReconnectedSucess = false;
                //isRecoonnectedSuccessTemp = false;
                isReconnected = true;//标定，已经重新链接了一次，开启下次链接计时（如果第一次链接不成功，下次链接将被定于60s以后，供服务器释放被占用的端口               
                //if (clientSocket1Temp == null)
                    clientSocket1Temp = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
                if (clientSocket1Temp.Poll(10, SelectMode.SelectRead))
                {
                    clientSocket1Temp.Shutdown(SocketShutdown.Both);
                }
                clientSocket1Temp.Connect(new IPEndPoint(IPAddress.Parse(textBox1.Text), int.Parse(textBox2.Text)));
                isConnected = true;
                clientSocket1 = clientSocket1Temp;
               // Thread.Sleep(2000);
                AppendString("clientSocket1 is ReConnecting... ");
                clientSocket2IsConnected = false;
            }
            catch
            {
                isConnected = false;
                AppendString("clintSocket1 链接失败，60s后重新链接...");
                
                //isReconnectedSucess = false;
            }

        }                      
        //定时发送senddate[]
        private void timer1_Tick(object sender, EventArgs e)
        {
            RegularlySending();
            time = 0;
        }
        //超时检测
        private void timer2_Tick(object sender, EventArgs e)
        {
            time++;
            
            if(time > 5)
            {
                RegularlySending ();
                time = 0;
            }
            //重新链接服务器计时
            if (isReconnected == true)
            {
                time2++;
                if (time2 > 60)
                {
                    //if (isReconnected && isRecoonnectedSuccessTemp = false && isReconnectedSucess = false)
                    //    isReconnectedSucess = false;
                    //超过60s 可与服务器二次建立链接
                    //if (isReconnectedSucess == false)
                    {
                        isReconnected = false;
                    }
                    time2 = 0;
                }
            }
            //超时重启检测
            if (!isConnected)
            {
                time3++;
                if (time3 > 300)
                {
                    time3 = 0;
                    //如果五分钟内未链接成功，则系统重启
                    WDT.ReBootSystem();

                }
            }
            else
            {
                time3 = 0;
            }
            //看门狗计时
            if (isEnableWDT)
            {
                wdtTime++;
                if (wdtTime > 10)
                {
                    wdtTime = 0;
                    WDT.FeedWDT();
                }
            }

        }       
        //北斗信息设置
       private void button2_Click_1(object sender, EventArgs e)
       {
           if(bdForm == null)
                bdForm = new BDForm(this);//实例化北斗对象
           bdForm.ShowDialog();
           //this.Hide();
       }
        //初始化北斗模块
       private void InitBD()
       {

       }
        //使用北斗事件
       private void button3_Click(object sender, EventArgs e)
       {
           btnDisUseBD.Enabled = true;
           btnUseBD.Enabled = false;
           isUseBD = true;
       }
        //禁用北斗事件
       private void btnDisUseBD_Click(object sender, EventArgs e)
       {
           btnDisUseBD.Enabled = false;
           btnUseBD.Enabled = true;
           isUseBD = false;
       }
       //关闭窗体
       protected override void OnClosing(CancelEventArgs e)
       {
           base.OnClosing(e);
           try
           {
               //textBox4.Text = "duakai lian jie ";
               ping.ClosePing();
               isConnected = false;
               clientSocket2IsConnected = false;
               t.Abort();
               clientSocket1.Shutdown(SocketShutdown.Both);
               clientSocket1.Close();
               Communication.ClosePort();
               bdCommunication.ClosePort();
               System.Diagnostics.Process.GetCurrentProcess().Kill();
           }
           catch
           {
               //textBox4.Text = "cheng xu guan bi chu xian wen ti ";
           }
       }
       //关闭socket释放资源
       private void CloseSocket()
       {
           try
           {
               clientSocket1.Shutdown(SocketShutdown.Both);
               clientSocket1.Close();
               clientSocket2.Shutdown(SocketShutdown.Both);
               clientSocket2.Close();

               clientSocket1 = null;
               clientSocket2 = null;
           }
           catch
           {
               clientSocket1 = null;
               clientSocket2 = null;
           }
       }
        //调整背光亮度
       private void button3_Click_1(object sender, EventArgs e)
       {
           BackLight.ChangeBackLight(100);
       }
        //重启系统
       private void button4_Click(object sender, EventArgs e)
       {
           WDT.ReBootSystem();
       }
        //IC检测
       private void button5_Click(object sender, EventArgs e)
       {
           bdCommunication.ICDetection();
       }
        //功率检测
       private void button6_Click(object sender, EventArgs e)
       {
           bdCommunication.PowerDetection();
       }
        //单次定位
       private void button7_Click(object sender, EventArgs e)
       {
           bdCommunication.SingleLocation();
       }
        //单次通信
       private void button8_Click(object sender, EventArgs e)
       {
           bdCommunication.SingleCommunication("123456", "012546832564");
       }
        //清空文本框
       private void button9_Click(object sender, EventArgs e)
       {
           //AppendString("");
           textBox4.Text = "";
       }
        //将光标滚动到文本框底部
       private void textBox4_TextChanged(object sender, EventArgs e)
       {
           textBox4.SelectionStart = textBox4.Text.Length;
           textBox4.ScrollToCaret();
       }

        #region TEST
       //捕获所有异常

       //private void CatchException()
       //{
       //    Application.EnableVisualStyles();
       //    Application.SetCompatibleTextRenderingDefault(false);

       //    //处理未捕获的异常
       //    Application.SetUnhandledExceptionMode(UnhandledExceptionMode.CatchException);
       //    //处理UI线程异常
       //    Application.ThreadException += new System.Threading.ThreadExceptionEventHandler(Application_ThreadException);
       //    //处理非UI线程异常
       //    AppDomain.CurrentDomain.UnhandledException += new UnhandledExceptionEventHandler(CurrentDomain_UnhandledException);

       //}

       #region TextBox显示模块
       /// <summary>
       /// 跨线程调用UI显示方法
       /// </summary>
       /// <param name="message"></param>
       private void TextChangeFunction()
       {
           if (this.textBox4.InvokeRequired)
           {
               TextChangeEvent tce = new TextChangeEvent(TextChangeFunction);
               this.Invoke(tce);
           }
           else
           {
               this.textBox4.Text += textMessage + Environment.NewLine;
           }
       }
       //异步调用TextBox
       private void Form1_OnMessageChange()
       {
           TextChangeFunction();
       }
       #endregion
        #endregion

    }

    ////finnal
}
